package cndw.core.dispatch;

import io.netty.util.internal.chmv8.ConcurrentHashMapV8;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import org.apache.commons.lang.builder.HashCodeBuilder;

import cndw.core.cfg.ServerConfig;
import cndw.core.dispatch.annotation.Action.CacheTarget;

/**
 * 一级缓存
 * 
 * @author zuojie.x
 */
final class L1Cache {
	/** 公共缓存 */
	private static Map<Integer, Response> publicCache = null;
	/** 私有缓存 */
	private static Map<Integer, Response> privateCache = null;
	/** 一级缓存是否开启 */
	public static boolean IsOpen = false;
	
	static {
		IsOpen = ServerConfig.booleanValue("L1Cache.Open");
		if (IsOpen) {
			publicCache = new ConcurrentHashMap<Integer, Response>(ServerConfig.intValue("L1Cache.Public.Size"));
			privateCache = new ConcurrentHashMapV8<Integer, Response>(ServerConfig.intValue("L1Cache.Private.Size"));
		}
	}
	
	public static void put(String playerId, ActionExecutor actionExecutor, Response res, CacheTarget target) {
		int hash = hash(playerId, actionExecutor, target);
		put(hash, res, target);
	}
	
	public static Response get(String playerId, ActionExecutor actionExecutor, CacheTarget target) {
		int hash = hash(playerId, actionExecutor, target);
		return get(hash, target);
	}
	
	/**
	 * 生成HASH码
	 * @param playerId
	 * @param actionExecutor
	 * @param target
	 * @return
	 */
	private static int hash(String playerId, ActionExecutor actionExecutor, CacheTarget target) {
		HashCodeBuilder builder = new HashCodeBuilder();
		switch (target) {
		case PUBLIC :
			break;
		case PRIVATE : 
			// 私有的加入玩家ID
			builder.append(playerId);
			break;
		default:
			break;
		}
		builder.append(actionExecutor.hashCode());
		return builder.toHashCode();
	}
	
	/**
	 * 加入缓存
	 * @param hash
	 * @param res
	 * @param target
	 */
	private static void put(int hash, Response res, CacheTarget target) {
		switch (target) {
		case PUBLIC :
			publicCache.put(hash, res);
			break;
		case PRIVATE :
			privateCache.put(hash, res);
			break;
		default:
			break;
		}
	}
	
	/**
	 * 从缓存中获取
	 * @param hash
	 * @param target
	 * @return
	 */
	private static Response get(int hash, CacheTarget target) {
		switch (target) {
		case PUBLIC :
			return publicCache.get(hash);
		case PRIVATE :
			return privateCache.get(hash);
		default:
			break;
		}
		return null;
	}
}
